package stock.nordnet;

import java.io.File;
import java.util.*;

import misc.Helpers;
import stock.Sale;

import com.gargoylesoftware.htmlunit.WebClient;
import com.gargoylesoftware.htmlunit.html.HtmlPage;
import com.gargoylesoftware.htmlunit.html.HtmlTable;

import ernie.database.Database;
import ernie.database.WebMysql;
import graph.Diagram;
import graph.HighLowDiagram;

public class NordnetScrape implements Runnable {

    public static void main(String[] args) {
        new NordnetScrape().run();
    }

    @Override
    public void run() {
        Timer timer = new Timer();

        TimerTask task = new TimerTask() {

            @Override
            public void run() {
                int dayOfWeek = Calendar.getInstance()
                        .get(Calendar.DAY_OF_WEEK);
                if (dayOfWeek != Calendar.SATURDAY
                        && dayOfWeek != Calendar.SUNDAY) {

                    Database db = new WebMysql("127.0.0.1", "highlow");
                    List<Sale> sales = getNordnetHighLowSales();
                    db.saveEntries(sales);

                    Calendar threeMonthsAgo = Calendar.getInstance();
                    threeMonthsAgo.add(Calendar.MONTH, -6);
                    Calendar tomorrow = Calendar.getInstance();
                    tomorrow.add(Calendar.DAY_OF_MONTH, 1);
                    tomorrow.set(Calendar.HOUR_OF_DAY, 18);

                    // Deletes all current files in the highlow folder
                    File directory = new File("C:\\wamp\\www\\graphs\\highlow");
                    for (File file : directory.listFiles()) {
                        file.delete();
                    }

                    for (int i = 0; i < sales.size(); i += 3) {
                        // TODO: Set date of the diagram!
                        String stockName = sales.get(i).getName();
                        Diagram diagram = new HighLowDiagram(stockName, 1024,
                                500, false);
                        diagram.setTimePeriod(threeMonthsAgo.getTimeInMillis(),
                                tomorrow.getTimeInMillis());
                        diagram.drawAndSaveDiagram(db, "highlow");
                        diagram.getDiagramPanel().removeAll();
                        diagram.getDiagramPanel().setEnabled(false);
                        diagram = null;
                        try {
                            Thread.sleep(2000);
                        } catch (InterruptedException e) {
                        }
                    }
                }
            }
        };

        // For testing:
        // task.run();

        Calendar nextTrigger = Calendar.getInstance();
        nextTrigger.set(Calendar.HOUR_OF_DAY, 19);
        if (Calendar.getInstance().get(Calendar.HOUR_OF_DAY) >= 19) {
            nextTrigger.add(Calendar.DAY_OF_MONTH, 1);
        }
        timer.schedule(task, new Date(nextTrigger.getTimeInMillis() + 2000),
                1000 * 3600 * 24);
    }

    public List<Sale> getNordnetHighLowSales() {
        System.out.println("Fetching nordnet sales page...");
        long startTime = System.currentTimeMillis();
        List<Sale> sales = new ArrayList<Sale>();
        HtmlPage salesPage = getPage("https://www.nordnet.se/mux/web/marknaden/kurslista/aktier.html?marknad=Norden&Sverige=on&Finland=on&Norge=on&Danmark=on&large=on&mid=on&small=on&sektor=0&subtyp=price&sortera=aktie&sorteringsordning=stigande");
        HtmlTable table = (HtmlTable) salesPage
                .getByXPath(
                        "/html/body/div[@id='container']/div[@id='content']/div[@id='contentPadding']/table[@id='kurstabell']")
                .get(0);
        long diff = System.currentTimeMillis() - startTime;
        System.out.println("Fetched nordnet sales page, " + diff + " ms");

        Calendar midDay = Calendar.getInstance();
        midDay.set(Calendar.HOUR_OF_DAY, 12);
        long time = midDay.getTimeInMillis();

        for (int i = 2; i < table.getRowCount(); i++) {
            try {
                String amountS = table.getCellAt(i, 9).asText()
                        .replace(" ", "");
                // Fast forwarding until no problems
                while (amountS.isEmpty() || amountS.contains("Omsatt")) {
                    i++;
                    amountS = table.getCellAt(i, 9).asText().replace(" ", "");
                }

                long amount = Long.parseLong(table.getCellAt(i, 9).asText()
                        .replace(" ", ""));
                double high = Double.parseDouble(table.getCellAt(i, 7).asText()
                        .replace(',', '.').replace(" ", ""));
                double low = Double.parseDouble(table.getCellAt(i, 8).asText()
                        .replace(',', '.').replace(" ", ""));
                double close = Double.parseDouble(table.getCellAt(i, 2)
                        .asText().replace(',', '.').replace(" ", ""));
                String name = table.getCellAt(i, 1).asText();
                name = Helpers.formatName(name);
                if (!sales.contains(new Sale(0, name, 0, 0))) {
                    sales.add(new Sale(time, name, high, amount));
                    sales.add(new Sale(time + 1, name, low, amount));
                    sales.add(new Sale(time + 2, name, close, amount));
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        return sales;
    }

    private HtmlPage getPage(String url) {
        WebClient client = Helpers.createNewAndSilenceWebClient();
        try {
            return (HtmlPage) client.getPage(url);
        } catch (Exception e) {
            e.printStackTrace();
            return getPage(url);
        }
    }

}
